// Copyright 2019, VIXL authors
// All rights reserved.
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are met:
//
//   * Redistributions of source code must retain the above copyright notice,
//     this list of conditions and the following disclaimer.
//   * Redistributions in binary form must reproduce the above copyright notice,
//     this list of conditions and the following disclaimer in the documentation
//     and/or other materials provided with the distribution.
//   * Neither the name of ARM Limited nor the names of its contributors may be
//     used to endorse or promote products derived from this software without
//     specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS CONTRIBUTORS "AS IS" AND
// ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
// WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
// DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE
// FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
// DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
// SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
// CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
// OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.

namespace vixl {
namespace aarch64 {

// This decode table is derived from the AArch64 ISA XML specification,
// available from https://developer.arm.com/products/architecture/a-profile/
//
// The data below are based on the "Index by Encoding" tables, reformatted into
// structures of C++ strings, suitable for processing into an instruction
// decoding tree.

// clang-format off
static const DecodeMapping kDecodeMapping[] = {
  { "Root",
    {28, 27, 26, 25},
    { {"0000", "DecodeReserved"},
      {"100x", "DecodeDataProcessingImmediate"},
      {"101x", "DecodeBranchesExceptionAndSystem"},
      {"x1x0", "DecodeLoadsAndStores"},
      {"x101", "DecodeDataProcessingRegister"},
      {"x111", "DecodeDataProcessingFPAndNEON"},
    },
  },

  { "DecodeReserved",
    {31, 30, 29, 24, 23, 22, 21, 20, 19, 18, 17, 16},
    { {"000000000000", "VisitReserved"},
      {"otherwise", "VisitUnallocated"},
    },
  },

  { "DecodeDataProcessingImmediate",
    {25, 24, 23},
    { {"00x", "VisitPCRelAddressing"},
      {"01x", "UnallocAddSubImmediate"},
      {"100", "UnallocLogicalImmediate"},
      {"101", "UnallocMoveWideImmediate"},
      {"110", "UnallocBitfield"},
      {"111", "UnallocExtract"},
    },
  },

  { "DecodeBranchesExceptionAndSystem",
    {31, 30, 29, 25, 24, 23, 22},
    { {"0100xxx", "UnallocConditionalBranch"},
      {"11000xx", "UnallocException"},
      {"1100100", "UnallocSystem"},
      {"1101xxx", "UnallocUnconditionalBranchToRegister"},
      {"x00xxxx", "VisitUnconditionalBranch"},
      {"x010xxx", "VisitCompareBranch"},
      {"x011xxx", "VisitTestBranch"},
    },
  },

  { "DecodeLoadsAndStores",
    {31, 29, 28, 26, 24, 23, 21},
    { {"x0000xx", "UnallocLoadStoreExclusive"},
      {"x01x0xx", "UnallocLoadLiteral"},
      {"x0101x0", "UnallocLoadStoreRCpcUnscaledOffset"},
      {"x10x00x", "UnallocLoadStorePairNonTemporal"},
      {"x10x01x", "UnallocLoadStorePairPostIndex"},
      {"x10x10x", "UnallocLoadStorePairOffset"},
      {"x10x11x", "UnallocLoadStorePairPreIndex"},
      {"0001000", "DecodeNEONLoadStoreMulti"},
      {"0001010", "UnallocNEONLoadStoreMultiStructPostIndex"},
      {"000110x", "DecodeNEONLoadStoreSingle"},
      {"000111x", "UnallocNEONLoadStoreSingleStructPostIndex"},
      {"x11x0x0", "DecodeLoadStore"},
      {"x11x0x1", "DecodeLoadStoreRegister"},
      {"x11x1xx", "UnallocLoadStoreUnsignedOffset"},
    },
  },

  { "DecodeDataProcessingRegister",
    {30, 28, 24, 23, 22, 21},
    { {"010110", "UnallocDataProcessing2Source"},
      {"110110", "UnallocDataProcessing1Source"},
      {"x00xxx", "UnallocLogicalShifted"},
      {"x01xx0", "UnallocAddSubShifted"},
      {"x01xx1", "UnallocAddSubExtended"},
      {"x10000", "UnallocAddSubWithCarry"},
      {"x10010", "DecodeCondCmp"},
      {"x10100", "UnallocConditionalSelect"},
      {"x11xxx", "UnallocDataProcessing3Source"},
    },
  },

  { "DecodeDataProcessingFPAndNEON",
    {31, 30, 29, 28, 24, 21},
    { {"0xx000", "DecodeNEONOther"},
      {"0xx001", "DecodeNEON3Op"},
      {"0xx01x", "DecodeNEONImmAndIndex"},
      {"01x100", "DecodeNEONScalarAnd3SHA"},
      {"01x101", "DecodeNEONScalarAnd2SHA"},
      {"01x11x", "DecodeNEONScalar"},
      {"x0x100", "UnallocFPFixedPointConvert"},
      {"x0x101", "DecodeFP"},
      {"x0x11x", "UnallocFPDataProcessing3Source"},
    },
  },

  { "DecodeNEONScalarAnd3SHA",
    {29, 23, 22, 15, 14, 11, 10},
    { {"0xx0x00", "VisitCrypto3RegSHA"},
      {"x000xx1", "UnallocNEONScalarCopy"},
      {"xxx1xx1", "UnallocNEONScalar3SameExtra"},
      {"xx100x1", "UnallocNEONScalar3SameFP16"},
    },
  },

  { "DecodeNEONScalarAnd2SHA",
    {29, 20, 19, 18, 17, 11, 10},
    { {"0010010", "VisitCrypto2RegSHA"},
      {"x000010", "UnallocNEONScalar2RegMisc"},
      {"x100010", "UnallocNEONScalarPairwise"},
      {"x110010", "UnallocNEONScalar2RegMiscFP16"},
      {"xxxxxx1", "UnallocNEONScalar3Same"},
      {"xxxxx00", "UnallocNEONScalar3Diff"},
    },
  },

  { "DecodeNEONScalar",
    {28, 23, 10},
    { {"101", "UnallocNEONScalarShiftImmediate"},
      {"1x0", "UnallocNEONScalarByIndexedElement"},
    },
  },

  { "DecodeNEONLoadStoreMulti",
    {20, 19, 18, 17, 16},
    { {"00000", "UnallocNEONLoadStoreMultiStruct"},
    },
  },

  { "DecodeNEONLoadStoreSingle",
    {20, 19, 18, 17, 16},
    { {"00000", "UnallocNEONLoadStoreSingleStruct"},
    },
  },

  { "DecodeNEONOther",
    {29, 23, 22, 15, 14, 11, 10},
    { {"0xx0x00", "UnallocNEONTable"},
      {"0xx0x10", "UnallocNEONPerm"},
      {"1xx0xx0", "UnallocNEONExtract"},
      {"x000xx1", "UnallocNEONCopy"},
      {"xx100x1", "UnallocNEON3SameFP16"},
      {"xxx1xx1", "UnallocNEON3SameExtra"},
    },
  },

  { "DecodeNEON2OpAndAcross",
    {30, 29, 20, 19, 18, 17},
    { {"100100", "VisitCryptoAES"},
      {"xx1100", "UnallocNEON2RegMiscFP16"},
      {"xx0000", "UnallocNEON2RegMisc"},
      {"xx1000", "UnallocNEONAcrossLanes"},
    },
  },

  { "DecodeNEON3Op",
    {11, 10},
    { {"00", "UnallocNEON3Different"},
      {"10", "DecodeNEON2OpAndAcross"},
      {"x1", "UnallocNEON3Same"},
    },
  },

  { "DecodeNEONImmAndIndex",
    {23, 22, 21, 20, 19, 10},
    { {"000001", "UnallocNEONModifiedImmediate"},
      {"0xxx11", "UnallocNEONShiftImmediate"},
      {"0xx1x1", "UnallocNEONShiftImmediate"},
      {"0x1xx1", "UnallocNEONShiftImmediate"},
      {"01xxx1", "UnallocNEONShiftImmediate"},
      {"xxxxx0", "UnallocNEONByIndexedElement"},
    },
  },

  { "DecodeFP",
    {15, 14, 13, 12, 11, 10},
    { {"000000", "UnallocFPIntegerConvert"},
      {"x10000", "UnallocFPDataProcessing1Source"},
      {"xx1000", "UnallocFPCompare"},
      {"xxx100", "UnallocFPImmediate"},
      {"xxxx01", "UnallocFPConditionalCompare"},
      {"xxxx10", "UnallocFPDataProcessing2Source"},
      {"xxxx11", "UnallocFPConditionalSelect"},
    },
  },

  { "DecodeLoadStore",
    {11, 10},
    { {"00", "UnallocLoadStoreUnscaledOffset"},
      {"01", "UnallocLoadStorePostIndex"},
      {"10", "VisitUnimplemented"},  // LoadStoreUnprivileged.
      {"11", "UnallocLoadStorePreIndex"},
    },
  },

  { "DecodeLoadStoreRegister",
    {11, 10},
    { {"00", "UnallocAtomicMemory"},
      {"10", "UnallocLoadStoreRegisterOffset"},
      {"x1", "UnallocLoadStorePAC"},
    },
  },

  { "DecodeCondCmp",
    {11},
    { {"0", "UnallocConditionalCompareRegister"},
      {"1", "UnallocConditionalCompareImmediate"},
    },
  },

  // Unallocation decode nodes. These are used to mark encodings within an
  // instruction class as unallocated.
  { "UnallocAddSubExtended",
    {12, 11, 10},
    { {"1x1", "VisitUnallocated"},
      {"11x", "VisitUnallocated"},
      {"otherwise", "UnallocAddSubExtended_2"},
    },
  },

  { "UnallocAddSubExtended_2",
    {23, 22},
    { {"1x", "VisitUnallocated"},
      {"x1", "VisitUnallocated"},
      {"otherwise", "VisitAddSubExtended"},
    },
  },

  { "UnallocAddSubImmediate",
    {23},
    { {"0", "VisitAddSubImmediate"},
      {"1", "VisitUnallocated"},
    },
  },

  { "UnallocAddSubShifted",
    {23, 22},
    { {"11", "VisitUnallocated"},
      {"otherwise", "UnallocAddSubShifted_2"},
    },
  },

  { "UnallocAddSubShifted_2",
    {31, 15},
    { {"01", "VisitUnallocated"},
      {"otherwise", "VisitAddSubShifted"},
    },
  },

  { "UnallocAddSubWithCarry",
    {15, 14, 13, 12, 11, 10},
    { {"000000", "VisitAddSubWithCarry"},
      {"x00001", "UnallocRotateRightIntoFlags"},
      {"xx0010", "UnallocEvaluateIntoFlags"},
      {"otherwise", "VisitUnallocated"},
    },
  },

  { "UnallocAtomicMemory",
    {26, 23, 22, 15, 14, 13, 12},
    { {"0xx1001", "VisitUnallocated"},
      {"0xx101x", "VisitUnallocated"},
      {"0xx1101", "VisitUnallocated"},
      {"0xx111x", "VisitUnallocated"},
      {"00x1100", "VisitUnallocated"},
      {"0111100", "VisitUnallocated"},
      {"1xxxxxx", "VisitUnallocated"},
      {"otherwise", "VisitAtomicMemory"},
    },
  },

  { "UnallocBitfield",
    {31, 30, 29, 22},
    { {"x11x", "VisitUnallocated"},
      {"0xx1", "VisitUnallocated"},
      {"1xx0", "VisitUnallocated"},
      {"otherwise", "VisitBitfield"},
    },
  },

  { "UnallocConditionalBranch",
    {24, 4},
    { {"00", "VisitConditionalBranch"},
      {"otherwise", "VisitUnallocated"},
    },
  },

  { "UnallocConditionalCompareImmediate",
    {10, 4, 29},
    { {"1xx", "VisitUnallocated"},
      {"x1x", "VisitUnallocated"},
      {"xx0", "VisitUnallocated"},
      {"otherwise", "VisitConditionalCompareImmediate"},
    },
  },

  { "UnallocConditionalCompareRegister",
    {10, 4, 29},
    { {"1xx", "VisitUnallocated"},
      {"x1x", "VisitUnallocated"},
      {"xx0", "VisitUnallocated"},
      {"otherwise", "VisitConditionalCompareRegister"},
    },
  },

  { "UnallocConditionalSelect",
    {11, 29},
    { {"00", "VisitConditionalSelect"},
      {"otherwise", "VisitUnallocated"},
    },
  },

  { "UnallocDataProcessing1Source",
    {31, 16, 14, 13, 12, 11, 10},
    { {"x0xx11x", "VisitUnallocated"},
      {"0000011", "VisitUnallocated"},
      {"1001xxx", "VisitUnallocated"},
      {"x01xxxx", "VisitUnallocated"},
      {"x0x1xxx", "VisitUnallocated"},
      {"01xxxxx", "VisitUnallocated"},
      {"111xx1x", "VisitUnallocated"},
      {"111x1xx", "VisitUnallocated"},
      {"1111xxx", "VisitUnallocated"},
      {"otherwise", "UnallocDataProcessing1Source_2"},
    },
  },

  { "UnallocDataProcessing1Source_2",
    {29, 20, 19, 18, 17, 15},
    { {"000000", "VisitDataProcessing1Source"},
      {"otherwise", "VisitUnallocated"},
    },
  },

  { "UnallocDataProcessing2Source",
    {31, 14, 13, 12, 11, 10},
    { {"x0000x", "VisitUnallocated"},
      {"x11xxx", "VisitUnallocated"},
      {"010x11", "VisitUnallocated"},
      {"110xx0", "VisitUnallocated"},
      {"110x0x", "VisitUnallocated"},
      {"otherwise", "UnallocDataProcessing2Source_2"},
    },
  },

  { "UnallocDataProcessing2Source_2",
    {29, 15},
    { {"00", "VisitDataProcessing2Source"},
      {"otherwise", "VisitUnallocated"},
    },
  },

  { "UnallocDataProcessing3Source",
    {23, 22, 21, 15, 31},
    { {"00100", "VisitUnallocated"},
      {"00110", "VisitUnallocated"},
      {"01000", "VisitUnallocated"},
      {"0101x", "VisitUnallocated"},
      {"011xx", "VisitUnallocated"},
      {"100xx", "VisitUnallocated"},
      {"10100", "VisitUnallocated"},
      {"10110", "VisitUnallocated"},
      {"11000", "VisitUnallocated"},
      {"1101x", "VisitUnallocated"},
      {"111xx", "VisitUnallocated"},
      {"otherwise", "UnallocDataProcessing3Source_2"},
    },
  },

  { "UnallocDataProcessing3Source_2",
    {30, 29},
    { {"00", "VisitDataProcessing3Source"},
      {"otherwise", "VisitUnallocated"},
    },
  },

  { "UnallocEvaluateIntoFlags",
    {31, 30, 29, 20, 19, 18},
    { {"001000", "UnallocEvaluateIntoFlags_2"},
      {"otherwise", "VisitUnallocated"},
    },
  },

  { "UnallocEvaluateIntoFlags_2",
    {17, 16, 15, 4, 3, 2, 1, 0},
    { {"00001101", "VisitEvaluateIntoFlags"},
      {"otherwise", "VisitUnallocated"},
    },
  },

  { "UnallocException",
    {23, 22, 21, 1, 0},
    { {"00000", "VisitUnallocated"},
      {"001x1", "VisitUnallocated"},
      {"0011x", "VisitUnallocated"},
      {"010x1", "VisitUnallocated"},
      {"0101x", "VisitUnallocated"},
      {"011xx", "VisitUnallocated"},
      {"100xx", "VisitUnallocated"},
      {"10100", "VisitUnallocated"},
      {"11xxx", "VisitUnallocated"},
      {"otherwise", "UnallocException_2"},
    },
  },

  { "UnallocException_2",
    {4, 3, 2},
    { {"000", "VisitException"},
      {"otherwise", "VisitUnallocated"},
    },
  },

  { "UnallocExtract",
    {30, 29, 21},
    { {"000", "UnallocExtract_2"},
      {"otherwise", "VisitUnallocated"},
    },
  },

  { "UnallocExtract_2",
    {31, 22, 15},
    { {"10x", "VisitUnallocated"},
      {"01x", "VisitUnallocated"},
      {"0x1", "VisitUnallocated"},
      {"otherwise", "VisitExtract"},
    },
  },

  { "UnallocFPCompare",
    {31, 29, 15, 14, 2, 1, 0},
    { {"0000000", "UnallocFPCompare_2"},
      {"otherwise", "VisitUnallocated"},
    },
  },

  { "UnallocFPCompare_2",
    {23, 22},
    { {"10", "VisitUnallocated"},
      {"otherwise", "VisitFPCompare"},
    },
  },

  { "UnallocFPConditionalCompare",
    {31, 29, 23, 22},
    { {"xx10", "VisitUnallocated"},
      {"x1xx", "VisitUnallocated"},
      {"1xxx", "VisitUnallocated"},
      {"otherwise", "VisitFPConditionalCompare"},
    },
  },

  { "UnallocFPConditionalSelect",
    {31, 29, 23, 22},
    { {"xx10", "VisitUnallocated"},
      {"x1xx", "VisitUnallocated"},
      {"1xxx", "VisitUnallocated"},
      {"otherwise", "VisitFPConditionalSelect"},
    },
  },

  { "UnallocFPDataProcessing1Source",
    {31, 29, 20},
    { {"000", "UnallocFPDataProcessing1Source_2"},
      {"otherwise", "VisitUnallocated"},
    },
  },

  { "UnallocFPDataProcessing1Source_2",
    {23, 22, 19, 18, 17, 16, 15},
    { {"0000100", "VisitUnallocated"},
      {"0000110", "VisitUnallocated"},
      {"0001101", "VisitUnallocated"},
      {"00101xx", "VisitUnallocated"},
      {"0011xxx", "VisitUnallocated"},
      {"0100101", "VisitUnallocated"},
      {"0101101", "VisitUnallocated"},
      {"01101xx", "VisitUnallocated"},
      {"0111xxx", "VisitUnallocated"},
      {"10xxxxx", "VisitUnallocated"},
      {"110011x", "VisitUnallocated"},
      {"1101101", "VisitUnallocated"},
      {"111xxxx", "VisitUnallocated"},
      {"otherwise", "VisitFPDataProcessing1Source"},
    },
  },

  { "UnallocFPDataProcessing2Source",
    {15, 14, 13, 12},
    { {"1xx1", "VisitUnallocated"},
      {"1x1x", "VisitUnallocated"},
      {"11xx", "VisitUnallocated"},
      {"otherwise", "UnallocFPDataProcessing2Source_2"},
    },
  },

  { "UnallocFPDataProcessing2Source_2",
    {31, 29, 23, 22},
    { {"xx10", "VisitUnallocated"},
      {"x1xx", "VisitUnallocated"},
      {"1xxx", "VisitUnallocated"},
      {"otherwise", "VisitFPDataProcessing2Source"},
    },
  },

  { "UnallocFPDataProcessing3Source",
    {31, 29, 23, 22},
    { {"xx10", "VisitUnallocated"},
      {"x1xx", "VisitUnallocated"},
      {"1xxx", "VisitUnallocated"},
      {"otherwise", "VisitFPDataProcessing3Source"},
    },
  },

  { "UnallocFPFixedPointConvert",
    {23, 22, 20, 19, 17, 16},
    { {"10xxxx", "VisitUnallocated"},
      {"xxx00x", "VisitUnallocated"},
      {"xxx11x", "VisitUnallocated"},
      {"xx0x0x", "VisitUnallocated"},
      {"xx1x1x", "VisitUnallocated"},
      {"otherwise", "UnallocFPFixedPointConvert_2"},
    },
  },

  { "UnallocFPFixedPointConvert_2",
    {29, 18},
    { {"00", "UnallocFPFixedPointConvert_3"},
      {"otherwise", "VisitUnallocated"},
    },
  },

  { "UnallocFPFixedPointConvert_3",
    {31, 15},
    { {"00", "VisitUnallocated"},
      {"otherwise", "VisitFPFixedPointConvert"},
    },
  },

  { "UnallocFPImmediate",
    {23, 22},
    { {"10", "VisitUnallocated"},
      {"otherwise", "UnallocFPImmediate_2"},
    },
  },

  { "UnallocFPImmediate_2",
    {31, 29, 9, 8, 7, 6, 5},
    { {"0000000", "VisitFPImmediate"},
      {"otherwise", "VisitUnallocated"},
    },
  },

  { "UnallocFPIntegerConvert",
    {29},
    { {"0", "UnallocFPIntegerConvert_2"},
      {"1", "VisitUnallocated"},
    },
  },

  { "UnallocFPIntegerConvert_2",
    {31, 23, 22, 20, 19, 18, 17, 16},
    { {"0001x11x", "VisitUnallocated"},
      {"0010x11x", "VisitUnallocated"},
      {"0011011x", "VisitUnallocated"},
      {"00111111", "VisitUnallocated"},
      {"010xx11x", "VisitUnallocated"},
      {"100xx11x", "VisitUnallocated"},
      {"1011x11x", "VisitUnallocated"},
      {"101x111x", "VisitUnallocated"},
      {"1101x11x", "VisitUnallocated"},
      {"110x011x", "VisitUnallocated"},
      {"xxx1x01x", "VisitUnallocated"},
      {"xxx1x10x", "VisitUnallocated"},
      {"xxxx110x", "VisitUnallocated"},
      {"xxxx101x", "VisitUnallocated"},
      {"otherwise", "VisitFPIntegerConvert"},
    },
  },

  { "UnallocLoadLiteral",
    {26, 31, 30},
    { {"111", "VisitUnallocated"},
      {"otherwise", "VisitLoadLiteral"},
    },
  },

  { "UnallocLoadStoreExclusive",
    {31, 23, 21, 14, 13, 12, 11, 10},
    { {"001xxxx0", "VisitUnallocated"},
      {"001xxx0x", "VisitUnallocated"},
      {"001xx0xx", "VisitUnallocated"},
      {"001x0xxx", "VisitUnallocated"},
      {"0010xxxx", "VisitUnallocated"},
      {"x11xxxx0", "VisitUnallocated"},
      {"x11xxx0x", "VisitUnallocated"},
      {"x11xx0xx", "VisitUnallocated"},
      {"x11x0xxx", "VisitUnallocated"},
      {"x110xxxx", "VisitUnallocated"},
      {"otherwise", "VisitLoadStoreExclusive"},
    },
  },

  { "UnallocLoadStorePAC",
    {31, 30, 26},
    { {"110", "VisitLoadStorePAC"},
      {"otherwise", "VisitUnallocated"},
    },
  },

  { "UnallocLoadStoreRCpcUnscaledOffset",
    {31, 30, 23, 22, 11, 10},
    { {"xxxxx1", "VisitUnallocated"},
      {"xxxx1x", "VisitUnallocated"},
      {"101100", "VisitUnallocated"},
      {"111000", "VisitUnallocated"},
      {"111100", "VisitUnallocated"},
      {"otherwise", "VisitLoadStoreRCpcUnscaledOffset"},
    },
  },

  { "UnallocLoadStorePairNonTemporal",
    {26, 31, 30, 22},
    { {"001x", "VisitUnallocated"},
      {"x11x", "VisitUnallocated"},
      {"otherwise", "VisitLoadStorePairNonTemporal"},
    },
  },

  { "UnallocLoadStorePairOffset",
    {26, 31, 30, 22},
    { {"0010", "VisitUnallocated"},
      {"x11x", "VisitUnallocated"},
      {"otherwise", "VisitLoadStorePairOffset"},
    },
  },

  { "UnallocLoadStorePairPostIndex",
    {26, 31, 30, 22},
    { {"0010", "VisitUnallocated"},
      {"x11x", "VisitUnallocated"},
      {"otherwise", "VisitLoadStorePairPostIndex"},
    },
  },

  { "UnallocLoadStorePairPreIndex",
    {26, 31, 30, 22},
    { {"0010", "VisitUnallocated"},
      {"x11x", "VisitUnallocated"},
      {"otherwise", "VisitLoadStorePairPreIndex"},
    },
  },

  { "UnallocLoadStorePostIndex",
    {26, 23, 22, 31, 30},
    { {"01011", "VisitUnallocated"},
      {"0111x", "VisitUnallocated"},
      {"11xx1", "VisitUnallocated"},
      {"11x1x", "VisitUnallocated"},
      {"otherwise", "VisitLoadStorePostIndex"},
    },
  },

  { "UnallocLoadStorePreIndex",
    {26, 23, 22, 31, 30},
    { {"01011", "VisitUnallocated"},
      {"0111x", "VisitUnallocated"},
      {"11xx1", "VisitUnallocated"},
      {"11x1x", "VisitUnallocated"},
      {"otherwise", "VisitLoadStorePreIndex"},
    },
  },

  { "UnallocLoadStoreRegisterOffset",
    {14},
    { {"0", "VisitUnallocated"},
      {"1", "UnallocLoadStoreRegisterOffset_2"},
    },
  },

  { "UnallocLoadStoreRegisterOffset_2",
    {26, 23, 22, 31, 30},
    { {"0111x", "VisitUnallocated"},
      {"11xx1", "VisitUnallocated"},
      {"11x1x", "VisitUnallocated"},
      {"otherwise", "VisitLoadStoreRegisterOffset"},
    },
  },

  { "UnallocLoadStoreUnscaledOffset",
    {26, 23, 22, 31, 30},
    { {"0111x", "VisitUnallocated"},
      {"11xx1", "VisitUnallocated"},
      {"11x1x", "VisitUnallocated"},
      {"otherwise", "VisitLoadStoreUnscaledOffset"},
    },
  },

  { "UnallocLoadStoreUnsignedOffset",
    {26, 23, 22, 31, 30},
    { {"0111x", "VisitUnallocated"},
      {"11xx1", "VisitUnallocated"},
      {"11x1x", "VisitUnallocated"},
      {"otherwise", "VisitLoadStoreUnsignedOffset"},
    },
  },

  { "UnallocLogicalImmediate",
    {31, 22},
    { {"01", "VisitUnallocated"},
      {"otherwise", "VisitLogicalImmediate"},
    },
  },

  { "UnallocLogicalShifted",
    {31, 15},
    { {"01", "VisitUnallocated"},
      {"otherwise", "VisitLogicalShifted"},
    },
  },

  { "UnallocMoveWideImmediate",
    {30, 29},
    { {"01", "VisitUnallocated"},
      {"otherwise", "UnallocMoveWideImmediate_2"},
    },
  },

  { "UnallocMoveWideImmediate_2",
    {31, 22},
    { {"01", "VisitUnallocated"},
      {"otherwise", "VisitMoveWideImmediate"},
    },
  },

  { "UnallocNEON2RegMisc",
    {16, 15, 14, 13, 12, 23, 22, 29},
    { {"00001xx1", "VisitUnallocated"},
      {"001011x1", "VisitUnallocated"},
      {"01010xx1", "VisitUnallocated"},
      {"011xx0xx", "VisitUnallocated"},
      {"011101x1", "VisitUnallocated"},
      {"1000xxxx", "VisitUnallocated"},
      {"10011xx0", "VisitUnallocated"},
      {"10101xxx", "VisitUnallocated"},
      {"101101xx", "VisitUnallocated"},
      {"101110x1", "VisitUnallocated"},
      {"101111xx", "VisitUnallocated"},
      {"110001x1", "VisitUnallocated"},
      {"111101xx", "VisitUnallocated"},
      {"111111x0", "VisitUnallocated"},
      {"otherwise", "VisitNEON2RegMisc"},
    },
  },

  { "UnallocNEON2RegMiscFP16",
    {29, 23, 22, 16, 15, 14, 13, 12},
    { {"xx0xxxxx", "VisitUnallocated"},
      {"xxx00xxx", "VisitUnallocated"},
      {"xxx010xx", "VisitUnallocated"},
      {"xxx10xxx", "VisitUnallocated"},
      {"xxx11110", "VisitUnallocated"},
      {"x0x011xx", "VisitUnallocated"},
      {"x0x11111", "VisitUnallocated"},
      {"x1x11100", "VisitUnallocated"},
      {"01x11111", "VisitUnallocated"},
      {"11x01110", "VisitUnallocated"},
      {"11x11000", "VisitUnallocated"},
      {"otherwise", "VisitNEON2RegMiscFP16"},
    },
  },

  { "UnallocNEON3Different",
    {15, 14, 13, 12, 29},
    { {"10011", "VisitUnallocated"},
      {"10111", "VisitUnallocated"},
      {"11011", "VisitUnallocated"},
      {"11101", "VisitUnallocated"},
      {"1111x", "VisitUnallocated"},
      {"otherwise", "VisitNEON3Different"},
    },
  },

  { "UnallocNEON3Same",
    {29, 23, 22, 15, 14, 13, 12, 11},
    { {"00111101", "VisitUnallocated"},
      {"01x11011", "VisitUnallocated"},
      {"01x11100", "VisitUnallocated"},
      {"01111101", "VisitUnallocated"},
      {"1xx10111", "VisitUnallocated"},
      {"10111001", "VisitUnallocated"},
      {"11x11011", "VisitUnallocated"},
      {"11x11111", "VisitUnallocated"},
      {"11111001", "VisitUnallocated"},
      {"otherwise", "VisitNEON3Same"},
    },
  },

  { "UnallocNEON3SameExtra",
    {29, 14, 13, 12, 11},
    { {"x0011", "VisitUnallocated"},
      {"x01xx", "VisitUnallocated"},
      {"00000", "VisitUnallocated"},
      {"00001", "VisitUnallocated"},
      {"01xxx", "VisitUnallocated"},
      {"111x1", "VisitUnallocated"},
      {"otherwise", "VisitNEON3SameExtra"},
    },
  },

  { "UnallocNEON3SameFP16",
    {29, 23, 13, 12, 11},
    { {"00101", "VisitUnallocated"},
      {"01011", "VisitUnallocated"},
      {"01100", "VisitUnallocated"},
      {"01101", "VisitUnallocated"},
      {"10001", "VisitUnallocated"},
      {"11001", "VisitUnallocated"},
      {"11011", "VisitUnallocated"},
      {"11111", "VisitUnallocated"},
      {"otherwise", "VisitNEON3SameFP16"},
    },
  },

  { "UnallocNEONAcrossLanes",
    {29, 23, 22, 16, 15, 14, 13, 12},
    { {"xxx0000x", "VisitUnallocated"},
      {"xxx00010", "VisitUnallocated"},
      {"xxx001xx", "VisitUnallocated"},
      {"xxx0100x", "VisitUnallocated"},
      {"xxx01011", "VisitUnallocated"},
      {"xxx01101", "VisitUnallocated"},
      {"xxx01110", "VisitUnallocated"},
      {"xxx10xxx", "VisitUnallocated"},
      {"xxx1100x", "VisitUnallocated"},
      {"xxx111xx", "VisitUnallocated"},
      {"00101100", "VisitUnallocated"},
      {"00101111", "VisitUnallocated"},
      {"01101100", "VisitUnallocated"},
      {"01101111", "VisitUnallocated"},
      {"1xx11011", "VisitUnallocated"},
      {"otherwise", "VisitNEONAcrossLanes"},
    },
  },

  { "UnallocNEONByIndexedElement",
    {29, 23, 22, 15, 14, 13, 12},
    { {"0010001", "VisitUnallocated"},
      {"0010101", "VisitUnallocated"},
      {"0011001", "VisitUnallocated"},
      {"00x0000", "VisitUnallocated"},
      {"00x0100", "VisitUnallocated"},
      {"0xx1111", "VisitUnallocated"},
      {"1000001", "VisitUnallocated"},
      {"1000011", "VisitUnallocated"},
      {"1000101", "VisitUnallocated"},
      {"1000111", "VisitUnallocated"},
      {"10x1000", "VisitUnallocated"},
      {"10x1100", "VisitUnallocated"},
      {"1110001", "VisitUnallocated"},
      {"1110011", "VisitUnallocated"},
      {"1110101", "VisitUnallocated"},
      {"1110111", "VisitUnallocated"},
      {"1xx1011", "VisitUnallocated"},
      {"x011001", "VisitUnallocated"},
      {"otherwise", "VisitNEONByIndexedElement"},
    },
  },

  { "UnallocNEONCopy",
    {14, 13, 12, 11, 30, 29},
    { {"xxxx01", "VisitUnallocated"},
      {"0010x0", "VisitUnallocated"},
      {"001100", "VisitUnallocated"},
      {"0100x0", "VisitUnallocated"},
      {"0110x0", "VisitUnallocated"},
      {"1xxxx0", "VisitUnallocated"},
      {"otherwise", "UnallocNEONCopy_2"},
    },
  },

  { "UnallocNEONCopy_2",
    {19, 18, 17, 16},
    { {"0000", "VisitUnallocated"},
      {"otherwise", "VisitNEONCopy"},
    },
  },

  { "UnallocNEONExtract",
    {23, 22},
    { {"00", "VisitNEONExtract"},
      {"otherwise", "VisitUnallocated"},
    },
  },

  { "UnallocNEONLoadStoreMultiStruct",
    {22, 15, 14, 13, 12},
    { {"00001", "VisitUnallocated"},
      {"00011", "VisitUnallocated"},
      {"00101", "VisitUnallocated"},
      {"01001", "VisitUnallocated"},
      {"01011", "VisitUnallocated"},
      {"011xx", "VisitUnallocated"},
      {"10001", "VisitUnallocated"},
      {"10011", "VisitUnallocated"},
      {"10101", "VisitUnallocated"},
      {"11001", "VisitUnallocated"},
      {"11011", "VisitUnallocated"},
      {"111xx", "VisitUnallocated"},
      {"otherwise", "VisitNEONLoadStoreMultiStruct"},
    },
  },

  { "UnallocNEONLoadStoreMultiStructPostIndex",
    {22, 15, 14, 13, 12},
    { {"00001", "VisitUnallocated"},
      {"00011", "VisitUnallocated"},
      {"00101", "VisitUnallocated"},
      {"01001", "VisitUnallocated"},
      {"01011", "VisitUnallocated"},
      {"011xx", "VisitUnallocated"},
      {"10001", "VisitUnallocated"},
      {"10011", "VisitUnallocated"},
      {"10101", "VisitUnallocated"},
      {"11001", "VisitUnallocated"},
      {"11011", "VisitUnallocated"},
      {"111xx", "VisitUnallocated"},
      {"otherwise", "VisitNEONLoadStoreMultiStructPostIndex"},
    },
  },

  { "UnallocNEONLoadSingleStruct",
    {21, 15, 14, 13, 12, 11, 10},
    { {"0010xx1", "VisitUnallocated"},
      {"0011xx1", "VisitUnallocated"},
      {"0100101", "VisitUnallocated"},
      {"0100x1x", "VisitUnallocated"},
      {"0101011", "VisitUnallocated"},
      {"01011x1", "VisitUnallocated"},
      {"0101x10", "VisitUnallocated"},
      {"01101xx", "VisitUnallocated"},
      {"01111xx", "VisitUnallocated"},
      {"1010xx1", "VisitUnallocated"},
      {"1011xx1", "VisitUnallocated"},
      {"1100011", "VisitUnallocated"},
      {"11001x1", "VisitUnallocated"},
      {"1100x10", "VisitUnallocated"},
      {"1101011", "VisitUnallocated"},
      {"11011x1", "VisitUnallocated"},
      {"1101x10", "VisitUnallocated"},
      {"11101xx", "VisitUnallocated"},
      {"11111xx", "VisitUnallocated"},
      {"otherwise", "VisitNEONLoadStoreSingleStruct"},
    },
  },

  { "UnallocNEONLoadStoreSingleStruct",
    {22},
    { {"0", "UnallocNEONStoreSingleStruct"},
      {"1", "UnallocNEONLoadSingleStruct"},
    },
  },

  { "UnallocNEONLoadSingleStructPostIndex",
    {21, 15, 14, 13, 12, 11, 10},
    { {"0010xx1", "VisitUnallocated"},
      {"0011xx1", "VisitUnallocated"},
      {"0100101", "VisitUnallocated"},
      {"0100x1x", "VisitUnallocated"},
      {"0101011", "VisitUnallocated"},
      {"01011x1", "VisitUnallocated"},
      {"0101x10", "VisitUnallocated"},
      {"01101xx", "VisitUnallocated"},
      {"01111xx", "VisitUnallocated"},
      {"1010xx1", "VisitUnallocated"},
      {"1011xx1", "VisitUnallocated"},
      {"1100011", "VisitUnallocated"},
      {"11001x1", "VisitUnallocated"},
      {"1100x10", "VisitUnallocated"},
      {"1101011", "VisitUnallocated"},
      {"11011x1", "VisitUnallocated"},
      {"1101x10", "VisitUnallocated"},
      {"11101xx", "VisitUnallocated"},
      {"11111xx", "VisitUnallocated"},
      {"otherwise", "VisitNEONLoadStoreSingleStructPostIndex"},
    },
  },

  { "UnallocNEONLoadStoreSingleStructPostIndex",
    {22},
    { {"0", "UnallocNEONStoreSingleStructPostIndex"},
      {"1", "UnallocNEONLoadSingleStructPostIndex"},
    },
  },

  { "UnallocNEONModifiedImmediate",
    {30, 29, 15, 14, 13, 12, 11},
    { { "x00xxx1", "VisitUnallocated"},
      { "x010xx1", "VisitUnallocated"},
      { "x0110x1", "VisitUnallocated"},
      { "x011101", "VisitUnallocated"},
      { "0111110", "VisitUnallocated"},
      { "x1xxxx1", "VisitUnallocated"},
      { "otherwise", "VisitNEONModifiedImmediate"},
    },
  },

  { "UnallocNEONPerm",
    {13, 12},
    { {"00", "VisitUnallocated"},
      {"otherwise", "VisitNEONPerm"},
    },
  },

  { "UnallocNEONScalar2RegMisc",
    {16, 15, 14, 13, 12, 23, 22, 29},
    { {"0000xxxx", "VisitUnallocated"},
      {"00010xxx", "VisitUnallocated"},
      {"0010xxxx", "VisitUnallocated"},
      {"00110xxx", "VisitUnallocated"},
      {"01010xx1", "VisitUnallocated"},
      {"011xx0xx", "VisitUnallocated"},
      {"011101x1", "VisitUnallocated"},
      {"01111xxx", "VisitUnallocated"},
      {"1000xxxx", "VisitUnallocated"},
      {"10010xx0", "VisitUnallocated"},
      {"10011xxx", "VisitUnallocated"},
      {"10101xxx", "VisitUnallocated"},
      {"101100x0", "VisitUnallocated"},
      {"101101xx", "VisitUnallocated"},
      {"10111xxx", "VisitUnallocated"},
      {"1100xxxx", "VisitUnallocated"},
      {"111001xx", "VisitUnallocated"},
      {"11110xxx", "VisitUnallocated"},
      {"111110xx", "VisitUnallocated"},
      {"111111x1", "VisitUnallocated"},
      {"otherwise", "VisitNEONScalar2RegMisc"},
    },
  },

  { "UnallocNEONScalar2RegMiscFP16",
    {29, 23, 22, 16, 15, 14, 13, 12},
    { {"xx0xxxxx", "VisitUnallocated"},
      {"xx100xxx", "VisitUnallocated"},
      {"xx1010xx", "VisitUnallocated"},
      {"xx110xxx", "VisitUnallocated"},
      {"xx11100x", "VisitUnallocated"},
      {"xx111110", "VisitUnallocated"},
      {"x01011xx", "VisitUnallocated"},
      {"x0111111", "VisitUnallocated"},
      {"x1101111", "VisitUnallocated"},
      {"x1111100", "VisitUnallocated"},
      {"11101110", "VisitUnallocated"},
      {"11111111", "VisitUnallocated"},
      {"otherwise", "VisitNEONScalar2RegMiscFP16"},
    },
  },

  { "UnallocNEONScalar3Diff",
    {14, 13, 12, 29},
    { {"000x", "VisitUnallocated"},
      {"0011", "VisitUnallocated"},
      {"010x", "VisitUnallocated"},
      {"0111", "VisitUnallocated"},
      {"100x", "VisitUnallocated"},
      {"1011", "VisitUnallocated"},
      {"11xx", "VisitUnallocated"},
      {"otherwise", "UnallocNEONScalar3Diff_2"},
    },
  },

  { "UnallocNEONScalar3Diff_2",
    {15},
    { {"0", "VisitUnallocated"},
      {"1", "VisitNEONScalar3Diff"},
    },
  },

  { "UnallocNEONScalar3Same",
    {15, 14, 13, 12, 11, 23, 22, 29},
    { {"00000xxx", "VisitUnallocated"},
      {"0001xxxx", "VisitUnallocated"},
      {"00100xxx", "VisitUnallocated"},
      {"011xxxxx", "VisitUnallocated"},
      {"1001xxxx", "VisitUnallocated"},
      {"1010xxxx", "VisitUnallocated"},
      {"10111xxx", "VisitUnallocated"},
      {"1100xxxx", "VisitUnallocated"},
      {"110100xx", "VisitUnallocated"},
      {"110101x0", "VisitUnallocated"},
      {"110110x1", "VisitUnallocated"},
      {"110111xx", "VisitUnallocated"},
      {"111001x0", "VisitUnallocated"},
      {"111010x0", "VisitUnallocated"},
      {"111011x0", "VisitUnallocated"},
      {"11110xxx", "VisitUnallocated"},
      {"111110x1", "VisitUnallocated"},
      {"111111x1", "VisitUnallocated"},
      {"otherwise", "VisitNEONScalar3Same"},
    },
  },

  { "UnallocNEONScalar3SameExtra",
    {29, 14, 13, 12, 11},
    { {"x001x", "VisitUnallocated"},
      {"x01xx", "VisitUnallocated"},
      {"x1xxx", "VisitUnallocated"},
      {"00000", "VisitUnallocated"},
      {"00001", "VisitUnallocated"},
      {"otherwise", "VisitNEONScalar3SameExtra"},
    },
  },

  { "UnallocNEONScalar3SameFP16",
    {29, 23, 13, 12, 11},
    { {"00011", "VisitNEONScalar3SameFP16"},
      {"00100", "VisitNEONScalar3SameFP16"},
      {"00111", "VisitNEONScalar3SameFP16"},
      {"01111", "VisitNEONScalar3SameFP16"},
      {"10100", "VisitNEONScalar3SameFP16"},
      {"10101", "VisitNEONScalar3SameFP16"},
      {"11010", "VisitNEONScalar3SameFP16"},
      {"11100", "VisitNEONScalar3SameFP16"},
      {"11101", "VisitNEONScalar3SameFP16"},
      {"otherwise", "VisitUnallocated"},
    },
  },

  { "UnallocNEONScalarByIndexedElement",
    {29, 23, 22, 15, 14, 13, 12},
    { {"0xx1111", "VisitUnallocated"},
      {"1000001", "VisitUnallocated"},
      {"1000101", "VisitUnallocated"},
      {"11x0001", "VisitUnallocated"},
      {"11x0101", "VisitUnallocated"},
      {"1xx0011", "VisitUnallocated"},
      {"1xx0111", "VisitUnallocated"},
      {"1xx1011", "VisitUnallocated"},
      {"1xx1100", "VisitUnallocated"},
      {"x010001", "VisitUnallocated"},
      {"x010101", "VisitUnallocated"},
      {"x011001", "VisitUnallocated"},
      {"xxx0000", "VisitUnallocated"},
      {"xxx0010", "VisitUnallocated"},
      {"xxx0100", "VisitUnallocated"},
      {"xxx0110", "VisitUnallocated"},
      {"xxx1000", "VisitUnallocated"},
      {"xxx1010", "VisitUnallocated"},
      {"xxx1110", "VisitUnallocated"},
      {"otherwise", "VisitNEONScalarByIndexedElement"},
    },
  },

  { "UnallocNEONScalarCopy",
    {14, 13, 12, 11},
    { {"0000", "UnallocNEONScalarCopy_2"},
      {"otherwise", "VisitUnallocated"},
    },
  },

  { "UnallocNEONScalarCopy_2",
    {19, 18, 17, 16},
    { {"0000", "VisitUnallocated"},
      {"otherwise", "UnallocNEONScalarCopy_3"},
    },
  },

  { "UnallocNEONScalarCopy_3",
    {29},
    { {"0", "VisitNEONScalarCopy"},
      {"1", "VisitUnallocated"},
    },
  },

  { "UnallocNEONScalarPairwise",
    {29, 23, 22, 16, 15, 14, 13, 12},
    { {"xxx00xxx", "VisitUnallocated"},
      {"xxx010xx", "VisitUnallocated"},
      {"xxx01110", "VisitUnallocated"},
      {"xxx10xxx", "VisitUnallocated"},
      {"xxx1100x", "VisitUnallocated"},
      {"xxx11010", "VisitUnallocated"},
      {"xxx111xx", "VisitUnallocated"},
      {"x1x01101", "VisitUnallocated"},
      {"00101100", "VisitUnallocated"},
      {"00101101", "VisitUnallocated"},
      {"00101111", "VisitUnallocated"},
      {"01101100", "VisitUnallocated"},
      {"01101111", "VisitUnallocated"},
      {"1xx11011", "VisitUnallocated"},
      {"otherwise", "VisitNEONScalarPairwise"},
    },
  },

  { "UnallocNEONScalarShiftImmediate",
    {15, 14, 13, 12, 11, 29},
    { {"00001x", "VisitUnallocated"},
      {"00011x", "VisitUnallocated"},
      {"00101x", "VisitUnallocated"},
      {"00111x", "VisitUnallocated"},
      {"010000", "VisitUnallocated"},
      {"01001x", "VisitUnallocated"},
      {"01011x", "VisitUnallocated"},
      {"011000", "VisitUnallocated"},
      {"01101x", "VisitUnallocated"},
      {"01111x", "VisitUnallocated"},
      {"100000", "VisitUnallocated"},
      {"100010", "VisitUnallocated"},
      {"101xxx", "VisitUnallocated"},
      {"110xxx", "VisitUnallocated"},
      {"11101x", "VisitUnallocated"},
      {"11110x", "VisitUnallocated"},
      {"otherwise", "UnallocNEONScalarShiftImmediate_2"},
    },
  },

  { "UnallocNEONScalarShiftImmediate_2",
    {22, 21, 20, 19},
    { {"0000", "VisitUnallocated"},
      {"otherwise", "VisitNEONScalarShiftImmediate"},
    },
  },

  { "UnallocNEONShiftImmediate",
    {15, 14, 13, 12, 11, 29},
    { {"00001x", "VisitUnallocated"},
      {"00011x", "VisitUnallocated"},
      {"00101x", "VisitUnallocated"},
      {"00111x", "VisitUnallocated"},
      {"010000", "VisitUnallocated"},
      {"01001x", "VisitUnallocated"},
      {"01011x", "VisitUnallocated"},
      {"011000", "VisitUnallocated"},
      {"01101x", "VisitUnallocated"},
      {"01111x", "VisitUnallocated"},
      {"10101x", "VisitUnallocated"},
      {"1011xx", "VisitUnallocated"},
      {"110xxx", "VisitUnallocated"},
      {"11101x", "VisitUnallocated"},
      {"11110x", "VisitUnallocated"},
      {"otherwise", "VisitNEONShiftImmediate"},
    },
  },

  { "UnallocNEONStoreSingleStruct",
    {21, 15, 14, 13, 12, 11, 10},
    { {"0010xx1", "VisitUnallocated"},
      {"0011xx1", "VisitUnallocated"},
      {"0100101", "VisitUnallocated"},
      {"0100x1x", "VisitUnallocated"},
      {"0101011", "VisitUnallocated"},
      {"01011x1", "VisitUnallocated"},
      {"0101x10", "VisitUnallocated"},
      {"1010xx1", "VisitUnallocated"},
      {"1011xx1", "VisitUnallocated"},
      {"1100011", "VisitUnallocated"},
      {"11001x1", "VisitUnallocated"},
      {"1100x10", "VisitUnallocated"},
      {"1101011", "VisitUnallocated"},
      {"11011x1", "VisitUnallocated"},
      {"1101x10", "VisitUnallocated"},
      {"x11xxxx", "VisitUnallocated"},
      {"otherwise", "VisitNEONLoadStoreSingleStruct"},
    },
  },

  { "UnallocNEONStoreSingleStructPostIndex",
    {21, 15, 14, 13, 12, 11, 10},
    { {"0010xx1", "VisitUnallocated"},
      {"0011xx1", "VisitUnallocated"},
      {"0100101", "VisitUnallocated"},
      {"0100x1x", "VisitUnallocated"},
      {"0101011", "VisitUnallocated"},
      {"01011x1", "VisitUnallocated"},
      {"0101x10", "VisitUnallocated"},
      {"1010xx1", "VisitUnallocated"},
      {"1011xx1", "VisitUnallocated"},
      {"1100011", "VisitUnallocated"},
      {"11001x1", "VisitUnallocated"},
      {"1100x10", "VisitUnallocated"},
      {"1101011", "VisitUnallocated"},
      {"11011x1", "VisitUnallocated"},
      {"1101x10", "VisitUnallocated"},
      {"x11xxxx", "VisitUnallocated"},
      {"otherwise", "VisitNEONLoadStoreSingleStructPostIndex"},
    },
  },

  { "UnallocNEONTable",
    {23, 22},
    { {"00", "VisitNEONTable"},
      {"otherwise", "VisitUnallocated"},
    },
  },

  { "UnallocRotateRightIntoFlags",
    {31, 30, 29, 4},
    { {"1010", "VisitRotateRightIntoFlags"},
      {"otherwise", "VisitUnallocated"},
    },
  },

  { "UnallocSystem",
    {21, 20, 19, 15, 14, 13, 12},
    { {"0000101", "VisitUnallocated"},
      {"000011x", "VisitUnallocated"},
      {"0001xxx", "VisitUnallocated"},
      {"100xxxx", "VisitUnallocated"},
      {"otherwise", "UnallocSystem_2"},
    },
  },

  { "UnallocSystem_2",
    {21, 20, 19, 15, 14, 13},
    { {"000000", "VisitUnallocated"},
      {"otherwise", "UnallocSystem_3"},
    },
  },

  { "UnallocSystem_3",
    {21, 20, 19, 16, 15, 14, 13},
    { {"0000001", "VisitUnallocated"},
      {"otherwise", "UnallocSystem_4"},
    },
  },

  { "UnallocSystem_4",
    {21, 20, 19, 17, 15, 14, 13},
    { {"0000001", "VisitUnallocated"},
      {"otherwise", "UnallocSystem_5"},
    },
  },

  { "UnallocSystem_5",
    {21, 20, 19, 18, 15, 14, 13},
    { {"0001001", "VisitUnallocated"},
      {"otherwise", "VisitSystem"},
    },
  },

  { "UnallocUnconditionalBranchToRegister",
    {15, 14, 13, 12},
    { {"0000", "UnallocUnconditionalBranchToRegister_2"},
      {"otherwise", "VisitUnallocated"},
    },
  },

  { "UnallocUnconditionalBranchToRegister_2",
    {20, 19, 18, 17, 16},
    { {"11111", "UnallocUnconditionalBranchToRegister_3"},
      {"otherwise", "VisitUnallocated"},
    },
  },

  { "UnallocUnconditionalBranchToRegister_3",
    {24, 23, 22, 21},
    { {"0011", "VisitUnallocated"},
      {"011x", "VisitUnallocated"},
      {"otherwise", "VisitUnconditionalBranchToRegister"},
    },
  },
};
// clang-format on

static const VisitorNode kVisitorNodes[] = {
#define VISITOR_NODES(A) {"Visit" #A, &Decoder::Visit##A},
    VISITOR_LIST(VISITOR_NODES)
#undef VISITOR_NODES
};

}  // namespace aarch64
}  // namespace vixl
